#include "mainwindow.h"
#include "ui_mainwindow.h"
#include"dialog.h"
#include"readname.h"
#include<QDebug>
#include<fstream>
#include<QMessageBox>
#include<QPen>
#include<QTimer>

#define ON
#ifdef ON
#define NEW
#define PEVENT
#define KEVENT
#endif
string nam[3]={"player1","player2","player3"};
int sco[3]={0};
MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    setWindowTitle(tr("snake"));
    setFixedSize(25*WIDTH,25*HEIGHT);


    //默认方向为RIGHT
    direc=RIGHT;
   //默认难度为LEVEL1
    level=1;
    speed=LEVEL[level];
    player="UnknowPlayer";
    score=0;
    //重置蛇的初始位置
    snake.clear();
    snake.push_back(QPoint(5,4));
    snake.push_back(QPoint(5,5));
    snake.push_back(QPoint(5,6));
    snake.push_back(QPoint(5,7));

    //初始化地图,1表示砖块，0表示空地
    QVector<int> temp1(WIDTH,1);
    map.push_back(temp1);
    QVector<int> temp2;
    temp2.push_back(1);
    for(int i=1;i<=WIDTH-2;i++)
        temp2.push_back(0);
    temp2.push_back(1);
    for(int i=1;i<=HEIGHT-2;i++)
        map.push_back(temp2);
    map.push_back(temp1);
    nam[0].clear();
    nam[1].clear();
    nam[2].clear();
    player.clear();
    loadscore();
    init_statuBar();

    //制作定时器，每x毫秒蛇自动前进
    timer=new QTimer(this);
    QObject::connect(timer,SIGNAL(timeout()),this,SLOT(automove()));
    qsrand(QTimer(0,0,0).secsTo(QTimer::currentTime()));

    QObject::connect(this,SIGNAL(gotin()),this,SLOT(addscore()));
    //update();

}
MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::on_action_Quit_triggered()
{
    save();
    qApp->exit();
}
#ifndef NEW
void MainWindow::on_action_New_triggered(){}
#else
void MainWindow::on_action_New_triggered()
{

     //默认方向为RIGHT
     direc=RIGHT;
     score=0;
     //重置蛇的初始位置
     snake.clear();
     snake.push_back(QPoint(5,4));
     snake.push_back(QPoint(5,5));
     snake.push_back(QPoint(5,6));
     snake.push_back(QPoint(5,7));

     //初始化地图,1表示砖块，0表示空地
     /*
      宽度WEIDTH,高度HEIGTH,"举个栗子"吧:
        111111111
        100000001
        100000001
        111111111
    */

     map.clear();
     QVector<int> temp1(WIDTH,1);
     map.push_back(temp1);
     QVector<int> temp2;
     temp2.push_back(1);
     for(int i=1;i<=WIDTH-2;i++)
         temp2.push_back(0);
     temp2.push_back(1);
     for(int i=1;i<=HEIGHT-2;i++)
         map.push_back(temp2);
     map.push_back(temp1);

     randapple();
     this->update();

    //启动定时器
     timer->start(speed);
     QSound sound("sound/darling.wav");
     sound.play();
     //QSound::play("F:/Code/Qt/snake2/sound/darling.wav");

     qDebug()<<"New 运行成功";

}
#endif
void MainWindow::randapple()
{
    apple.setX(qrand()%WIDTH);
    apple.setY(qrand()%HEIGHT);
    if(map[apple.y()][apple.x()]!=0)
        this->randapple();
    else if(qFind(snake.begin(),snake.end(),apple)!=snake.end())
            this->randapple();
    else
        qDebug()<<"randapple 运行成功";
}

void MainWindow::move(direction direc)
{
    QVector<QPoint> temp(snake.size());
    switch(direc)
    {
        case UP:
        {
        temp[0]=QPoint(snake[0].x(),snake[0].y()-1);
        qCopy(snake.begin(),snake.end()-1,temp.begin()+1);
        snake=temp;
        break;
        }
        case DOWN:
        {
        temp[0]=QPoint(snake[0].x(),snake[0].y()+1);
        qCopy(snake.begin(),snake.end()-1,temp.begin()+1);
        snake=temp;
        break;
        }
        case LEFT:
        {
        temp[0]=QPoint(snake[0].x()-1,snake[0].y());
        qCopy(snake.begin(),snake.end()-1,temp.begin()+1);
        snake=temp;
        break;
        }
        case RIGHT:
        {
        temp[0]=QPoint(snake[0].x()+1,snake[0].y());
        qCopy(snake.begin(),snake.end()-1,temp.begin()+1);
        snake=temp;
        break;
        }
    }
    qDebug()<<"move 运行成功";
}

void MainWindow::eat()
{
    //这里需要注意容器的最后一个元素是end()-1,不是end()
    //蛇尾朝右前进
    if(snake[snake.size()-1].x()==snake[snake.size()-2].x()&&snake[snake.size()-1].y()<snake[snake.size()-2].y())
        snake.push_back(QPoint(snake[snake.size()-1].x(),snake[snake.size()-1].y()-1));
    //蛇尾朝左前进
    if(snake[snake.size()-1].x()==snake[snake.size()-2].x()&&snake[snake.size()-1].y()>snake[snake.size()-2].y())
        snake.push_back(QPoint(snake[snake.size()-1].x(),snake[snake.size()-1].y()+1));
    //蛇尾朝上前进
    if(snake[snake.size()-1].y()==snake[snake.size()-2].y()&&snake[snake.size()-1].x()>snake[snake.size()-2].x())
        snake.push_back(QPoint(snake[snake.size()-1].x()+1,snake[snake.size()-1].y()));
    //蛇尾朝下前进
    if(snake[snake.size()-1].y()==snake[snake.size()-2].x()&&snake[snake.size()-1].x()<snake[snake.size()-2].x())
        snake.push_back(QPoint(snake[snake.size()-1].x()-1,snake[snake.size()-1].y()));
    //撞墙
    if(map[snake[snake.size()-1].y()][snake[snake.size()-1].x()]==1)
        snake.pop_back();
    score+=level;
    emit gotin();
    QSound sound("sound/eat.wav");
    sound.play();
    qDebug()<<"eat 运行成功";
}

#ifndef PEVENT
void MainWindow::paintEvent(QPaintEvent *event){}
#else
void MainWindow::paintEvent(QPaintEvent *event)
{
    QPainter mypainter(this);
    mypainter.setPen(QPen(Qt::black,1));
    //画地图
    for(QVector< QVector<int> >::size_type i=0;i!=WIDTH;i++)
        for(QVector<int>::size_type j=0;j!=HEIGHT;j++ )
            switch(map.at(j).at(i))
            {
                case 0:
                    mypainter.setBrush(Qt::black);
                    mypainter.drawPixmap(i*25,j*25,QPixmap(":/xsd/images/ground.png"));
                    break;
                case 1:
                    mypainter.setBrush(Qt::red);
                    mypainter.drawPixmap(i*25,j*25,QPixmap(":/xsd/images/stone.png"));
                    break;
            }
    //画苹果
    mypainter.drawPixmap(apple.x()*25,apple.y()*25,QPixmap(":/xsd/images/apple.png"));
    //画蛇

    //蛇头
    switch(direc)
    {
        case UP:
            mypainter.drawPixmap(snake[0].x()*25,snake[0].y()*25,QPixmap(":/xsd/images/head_up.png"));
            break;
        case DOWN:
            mypainter.drawPixmap(snake[0].x()*25,snake[0].y()*25,QPixmap(":/xsd/images/head_down.png"));
            break;
        case LEFT:
            mypainter.drawPixmap(snake[0].x()*25,snake[0].y()*25,QPixmap(":/xsd/images/head_left.png"));
            break;
        case RIGHT:
            mypainter.drawPixmap(snake[0].x()*25,snake[0].y()*25,QPixmap(":/xsd/images/head_right.png"));
            break;
    }

    //蛇身
    for(QVector<QPoint>::size_type i=1;i!=snake.size();i++)
    {
        mypainter.drawPixmap(snake[i].x()*25,snake[i].y()*25,QPixmap(":/xsd/images/body.png"));
    }
    //qDebug()<<"painter 运行成功";
    event->accept();
}
#endif

#ifndef KEVENT
void MainWindow::keyPressEvent(QKeyEvent *event){}
#else
void MainWindow::keyPressEvent(QKeyEvent *event)
{
    switch(event->key())
    {
        case    Qt::Key_Up:
            //蛇头和脖子没有都朝上前进
            if(snake[0].y()!=snake[1].y()+1)
                move(UP);
            if(snake[0]==apple)
            {
                eat();
                randapple();
            }
            if(map[snake[0].y()][snake[0].x()]==1)
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞墙了！"));
                gameover();
            }
            if(qFind(snake.begin()+1,snake.end(),snake[0])!=snake.end())
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞蛇了"));
                gameover();
            }
            direc=UP;
            update();
            break;
    case Qt::Key_Down:
            if(snake[0].y()!=snake[1].y()-1)
                move(DOWN);
            if(snake[0]==apple)
            {
                eat();
                randapple();
            }
            if(map[snake[0].y()][snake[0].x()]==1)
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞墙了！"));
                gameover();
            }
            if(qFind(snake.begin()+1,snake.end(),snake[0])!=snake.end())
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞蛇了"));
                gameover();
            }
            direc=DOWN;
            update();
            break;
        case Qt::Key_Right:
            if(snake[0].x()!=snake[1].x()-1)
                move(RIGHT);
            if(snake[0]==apple)
            {
                eat();
                randapple();
            }
            if(map[snake[0].y()][snake[0].x()]==1)
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞墙了！"));
                gameover();
            }
            if(qFind(snake.begin()+1,snake.end(),snake[0])!=snake.end())
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞蛇了"));
                gameover();
            }
            direc=RIGHT;
            update();
            break;
        case Qt::Key_Left:
            if(snake[0].x()!=snake[1].x()+1)
                move(LEFT);
            if(snake[0]==apple)
            {
                eat();
                randapple();
            }
            if(map[snake[0].y()][snake[0].x()]==1)
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞墙了！"));
                gameover();
            }
            if(qFind(snake.begin()+1,snake.end(),snake[0])!=snake.end())
            {
                 timer->stop();
                QMessageBox::information(this,tr("游戏结束"),tr("你撞蛇了"));
                gameover();
            }
            direc=LEFT;
            update();
            break;
    }
    qDebug()<<"kevent 运行成功";
    event->accept();
}
#endif

void MainWindow::automove()
{
    move(direc);
    if(snake[0]==apple)
    {
        eat();
        randapple();
    }
    if(map[snake[0].y()][snake[0].x()]==1)
    {
         timer->stop();
        QMessageBox::information(this,tr("游戏结束"),tr("你撞墙了！"));
        gameover();
    }
    if(qFind(snake.begin()+1,snake.end(),snake[0])!=snake.end())
    {
         timer->stop();
        QMessageBox::information(this,tr("游戏结束"),tr("你撞蛇了"));
        gameover();
    }
    update();
    qDebug()<<"automove 运行成功";

}
void MainWindow::gameover()
{
    int f=-1;
    for(int i=0;i<3;i++)
    {
        if(score>=sco[i])
        {
            f=i;
            break;
        }
    }
    if(0<=f&&f<=2)
    {
        getname();
        switch(f)
        {
        case 0:
            sco[2]=sco[1];
            sco[1]=sco[0];
            sco[0]=score;
            nam[2]=nam[1];
            nam[1]=nam[0];
            nam[0]=player;
            break;
        case 1:
            sco[2]=sco[1];
            sco[1]=score;
            nam[2]=nam[1];
            nam[1]=player;
            break;
        case 2:
            sco[2]=score;
            nam[2]=player;
            break;
            default:break;
        }
        save();
    }


    exit(EXIT_SUCCESS);

}
void MainWindow::save()
{
    fstream file1;
    file1.open("score.dat",ios::out);
    if(file1)
    {
       for(int i=0;i<3;i++)
       {
           if(nam[i].length()==0)
               nam[i]="UnknowPlayer";
           file1<<nam[i]<<" "<<sco[i]<<endl;

       }
        file1.close();
    }
    else
    {
        QMessageBox message(QMessageBox::NoIcon, "报告", "保存失败");
        message.exec();
    }
}

void MainWindow::on_action_Pause_triggered()
{
  timer->stop();
}

void MainWindow::on_action_Continue_triggered()
{
    timer->start(speed);
}

void MainWindow::on_action_level1_triggered()
{
    timer->stop();
    level=1;
    speed=LEVEL[level];

}
void MainWindow::on_action_level2_triggered()
{
    timer->stop();
    level=2;
    speed=LEVEL[level];

}

void MainWindow::on_action_level3_triggered()
{
    timer->stop();
    level=3;
    speed=LEVEL[level];

}

void MainWindow::on_action_level4_triggered()
{
    timer->stop();
    level=4;
    speed=LEVEL[level];

}

void MainWindow::on_action_level5_triggered()
{
    timer->stop();
    level=5;
    speed=LEVEL[level];

}

void MainWindow::on_action_help_triggered()
{
    QMessageBox message(QMessageBox::NoIcon, "说明", "使用键盘上的 ↑ ↓ ← → 四个按键控制蛇\n");
    message.setIconPixmap(QPixmap(":/fire/icon/snake.ico"));
    message.exec();
}

void MainWindow::on_action_author_triggered()
{
    QMessageBox message(QMessageBox::NoIcon, "writer", "Made by onlyn");
    message.setIconPixmap(QPixmap(":/fire/icon/author.ico"));
    message.exec();
}
void MainWindow::loadscore()
{
       fstream file1;
       file1.open("score.dat",ios::in);
       if(file1)
       {
           for(int i=0;i<3;i++)
               file1>>nam[i]>>sco[i];

        file1.close();
       }
       else
       {
            QMessageBox message(QMessageBox::NoIcon, "报告", "读取失败");
            message.exec();
       }


}
void MainWindow::on_action_Score_triggered()
{
    Dialog dia;
    dia.exec();
}
void MainWindow::getname()
{
    readname *rname;
    rname=new readname();
    if(connect(rname,SIGNAL(sendData(string)),this,SLOT(receiveData(string))))
        qDebug()<<"rname 连接成功";
    else
        qDebug()<<"rname 连接失败";
    rname->exec();

}
void MainWindow::receiveData(string rec)
{
    player=rec;
    qDebug( )<<"用户名字是:"<< QString::fromStdString(player);
}
void MainWindow::init_statuBar()
{
    QStatusBar * bar=ui->statusBar;
    first_statusLabel=new QLabel;
       first_statusLabel->setMinimumSize(150,20);
       first_statusLabel->setFrameShape(QFrame::WinPanel);
       first_statusLabel->setFrameShadow(QFrame::Sunken);
       second_statusLabel=new QLabel;
       second_statusLabel->setMinimumSize(150,20);
       second_statusLabel->setFrameShape(QFrame::WinPanel);
       second_statusLabel->setFrameShadow(QFrame::Sunken);
       bar->addWidget(first_statusLabel);
       bar->addWidget(second_statusLabel);
       first_statusLabel->setText(tr("welcome"));
       second_statusLabel->setText(tr("Fire"));
}
void MainWindow::addscore()
{
    second_statusLabel->setText(tr("当前得分: %1").arg(score));
}
